package com.shangxian.giveithome.exception;


import com.shangxian.giveithome.code.CommonCode;
import com.shangxian.giveithome.code.ImgFeiCode;
import com.shangxian.giveithome.result.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpStatus;
import org.springframework.validation.BindException;
import org.springframework.validation.ObjectError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.multipart.MaxUploadSizeExceededException;

import javax.validation.ConstraintViolationException;
import java.util.ArrayList;
import java.util.List;

@Slf4j
@ControllerAdvice
public class UnifiedException {

    @ExceptionHandler(ApiException.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.INTERNAL_SERVER_ERROR)
    public Result UserError(ApiException e) {
        log.error("Code:{} - ApiException:{}", e.getResult().getCode(), e.getResult().getMessage());
        return e.getResult();
    }

    @ExceptionHandler(BindException.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.BAD_REQUEST)
    public Result BindException(BindException e) {
        List<String> errors = new ArrayList<>();
        for (ObjectError ay : e.getAllErrors()) {
            errors.add(ay.getDefaultMessage());
        }
        log.error("Code:400 参数非法:{}", errors.toString());
        return Result.error(CommonCode.PARAMETER_ERROR, errors);
    }

    @ExceptionHandler(MethodArgumentNotValidException.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.BAD_REQUEST)
    public Result MethodArgumentNotValidException(MethodArgumentNotValidException e) {
        List<String> errorMess = new ArrayList<String>();
        e.getBindingResult().getAllErrors().forEach((s) -> {
            errorMess.add(s.getDefaultMessage());
        });
        log.error("Code:400 参数非法:{}", errorMess.toString());
        return Result.error(CommonCode.PARAMETER_ERROR, errorMess);
    }

    @ExceptionHandler(ConstraintViolationException.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.BAD_REQUEST)
    public Result BindException(ConstraintViolationException e) {
        List<String> errors = new ArrayList<>();
        List<String> parent = new ArrayList<>();
        e.getConstraintViolations().forEach(er -> {
            errors.add(er.getMessage());
            er.getPropertyPath().forEach(pr -> {
                parent.add(pr.getName());
            });
        });
        log.error(e.getMessage());
        return Result.error(CommonCode.PARAMETER_ERROR, errors);
    }

    @ExceptionHandler(MaxUploadSizeExceededException.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.BAD_REQUEST)
    public Result MaxUploadSizeExceededException(MaxUploadSizeExceededException e) {
        log.error("MaxUploadSizeExceededException:{}", e.getMessage());
        return Result.error(ImgFeiCode.FILE_SIZE);
    }
}
